package com.tgy.clickhouse.exception.handler;

import com.tgy.clickhouse.exception.OperationResult;
import com.tgy.clickhouse.exception.PredictionGlobalException;
import com.tgy.clickhouse.exception.error.BasicErrorType;
import lombok.extern.slf4j.Slf4j;
import org.springframework.web.HttpMediaTypeNotSupportedException;
import org.springframework.web.HttpRequestMethodNotSupportedException;
import org.springframework.web.bind.MissingServletRequestParameterException;
import org.springframework.web.bind.annotation.ControllerAdvice;
import org.springframework.web.bind.annotation.ExceptionHandler;
import org.springframework.web.bind.annotation.ResponseBody;
import org.springframework.web.servlet.NoHandlerFoundException;

import javax.servlet.http.HttpServletRequest;

/**
 * 全局异常处理器
 * @author tgy
 * @date 2021/9/2
 */
@ControllerAdvice
@Slf4j
public class PredictionGlobalExceptionHandler {

    /**
     * 自定义全局异常
     */
    @ExceptionHandler(value = PredictionGlobalException.class)
    @ResponseBody
    public OperationResult<Object> handlerPredictionGlobalException(PredictionGlobalException e){
        log.error("PredictionGlobalException，原因是: {}", e.getMessage());
        return new OperationResult<>(e.getBasicErrorType());
    }

    /**
     * Controller上一层相关异常（部分）
     *
     * @param e 异常
     * @return 异常结果
     */
    @ExceptionHandler({
            NoHandlerFoundException.class,
            HttpRequestMethodNotSupportedException.class,
            HttpMediaTypeNotSupportedException.class,
            MissingServletRequestParameterException.class
    })
    @ResponseBody
    public OperationResult<Object> handleServletException(Exception e) {
        log.error("handleServletException: " + e.getMessage(), e);
        OperationResult<Object> operationResult = new OperationResult<>();
        operationResult.setStatus(OperationResult.STATUS_FAILURE);
        if(e instanceof NoHandlerFoundException) {
            operationResult = new OperationResult<>(BasicErrorType.METHOD_NOT_FOUND_ERROR);
        } else if (e instanceof HttpRequestMethodNotSupportedException) {
            operationResult = new OperationResult<>(BasicErrorType.METHOD_NOT_SUPPORT_ERROR);
        } else if (e instanceof MissingServletRequestParameterException) {
            operationResult = new OperationResult<>(BasicErrorType.REQUEST_PARAMETER_MISS_ERROR);
        } else if (e instanceof HttpMediaTypeNotSupportedException) {
            operationResult = new OperationResult<>(BasicErrorType.MEDIA_TYPE_NOT_SUPPORT_ERROR);
        }

        return operationResult;
    }

    /**
     * 空指针异常
     */
    @ExceptionHandler(value =NullPointerException.class)
    @ResponseBody
    public OperationResult<Object> handlerNullPointerException(HttpServletRequest req, Exception e){
        log.error("空指针异常！原因是:", e);
        return new OperationResult<>(BasicErrorType.NULLPOINTER_SYSTEM_ERROR);
    }

    /**
     * 其他异常
     */
    @ExceptionHandler(value =Exception.class)
    @ResponseBody
    public OperationResult<Object> handlerException(HttpServletRequest req, Exception e){
        log.error("未知异常！原因是:", e);
        return new OperationResult<>(BasicErrorType.UNKNOW_ERROR);
    }
}
